#ifndef __TINYSRV_REF_OBJECT_H__
#define __TINYSRV_REF_OBJECT_H__

#include "non_copyable.h"
#include "ref_obj_ptr.h"

namespace tinySrv
{

  template <typename T>
  class RefObject
    : private NonCopyable
    , public T
  {
  public:
    virtual unsigned long AddRef()
    {
      return __sync_fetch_and_add(&Counter, 1) + 1;
    }
    virtual unsigned long Release()
    {
      unsigned long Ret = __sync_fetch_and_sub(&Counter, 1) - 1;
      if (!Ret)
        delete this;
      return Ret;
    }
    
    static RefObjPtr<RefObject<T> > Create()
    {
      return RefObjPtr<RefObject<T> >(new RefObject<T>);
    }
    
  private:
    unsigned long volatile Counter;
    
    RefObject()
      : Counter(0)
    {
    }
    virtual ~RefObject()
    {
    }
  };
  
}

#endif  // !__TINYSRV_REF_OBJECT_H__
